﻿Imports System.Security.Cryptography
Imports System.Configuration
Imports System.Linq
Imports Microsoft.Vbe.Interop
Imports System.Text.RegularExpressions
Imports System.Text

Public Class GeneralClassDAL
    Public Shared dc As New TanNamChinhDataContext
    Private Const KEY_ENCRYPT As String = "TNC"
    Private Const KEY_CONNECTSTRING As String = "TNCVB.My.MySettings.TanNamChinhConnectionString"
    ''' <summary>
    ''' Giải mã connectstring, copy đoạn code này vào class TanNamChinh.designer.vb của TanNamChinh.dbml
    ''' =====================================
    ''' Public Sub New()
    ''' MyBase.New(GeneralClass.GetConnectString(), mappingSource)
    ''' OnCreated()
    ''' End Sub
    ''' =====================================
    ''' </summary>
    ''' <returns></returns>
    ''' <remarks></remarks>
    Public Shared Function GetConnectString() As String
        Dim connectionString As String = ""
        Try
            Dim connectStringSettings As ConnectionStringSettings = ConfigurationManager.ConnectionStrings(KEY_CONNECTSTRING)
            connectionString = connectStringSettings.ConnectionString

            Dim encrypt_user As String = GetGiaTriThanhPhan(connectionString, "User ID")
            Dim encrypt_pass As String = GetGiaTriThanhPhan(connectionString, "Password")
            Dim decrypt_user As String = DeCrypt(encrypt_user, KEY_ENCRYPT)
            Dim decrypt_pass As String = DeCrypt(encrypt_pass, KEY_ENCRYPT)
            connectionString = connectionString.Replace(String.Format("User ID={0}", encrypt_user), String.Format("User ID={0}", decrypt_user))
            connectionString = connectionString.Replace(String.Format("Password={0}", encrypt_pass), String.Format("Password={0}", decrypt_pass))
        Catch ex As Exception
            connectionString = ""
        End Try
        Return connectionString
    End Function

    Public Shared Function ChangeConnectString(ByVal connectString As String) As String
        Dim server As String
        Dim database As String
        Dim user As String
        Dim pass As String
        Try
            server = GeneralClassDAL.GetGiaTriThanhPhan(connectString, "Data Source")
            database = GeneralClassDAL.GetGiaTriThanhPhan(connectString, "Initial Catalog")
            user = GeneralClassDAL.GetGiaTriThanhPhan(connectString, "User ID")
            pass = GeneralClassDAL.GetGiaTriThanhPhan(connectString, "Password")
            'Lưu vào file config
            connectString = ChangeConnectString(server, database, user, pass)
        Catch ex As Exception
            Throw ex
        End Try
        Return connectString
    End Function

    ''' <summary>
    ''' Connect database with new configuration
    ''' </summary>
    ''' <param name="server"></param>
    ''' <param name="database"></param>
    ''' <param name="user"></param>
    ''' <param name="pass"></param>
    ''' <returns></returns>
    ''' <remarks></remarks>
    Public Shared Function ChangeConnectString(ByVal server As String, ByVal database As String, ByVal user As String, ByVal pass As String) As String
        Dim connectString As String = ""
        Try
            'Dim connectStringName = KEY_CONNECTSTRING ' "TNCVB.My.MySettings.TanNamChinhConnectionString"
            Dim config = ConfigurationManager.OpenExeConfiguration(ConfigurationUserLevel.None)
            'Dim connectStringSettings As ConnectionStringSettings = ConfigurationManager.ConnectionStrings(KEY_CONNECTSTRING)
            user = EnCrypt(user, KEY_ENCRYPT)
            pass = EnCrypt(pass, KEY_ENCRYPT)
            connectString = String.Format("Data Source={0};Initial Catalog={1};Persist Security Info=True;User ID={2};Password={3}", server, database, user, pass)
            config.ConnectionStrings.ConnectionStrings(KEY_CONNECTSTRING).ConnectionString = connectString

            config.Save(ConfigurationSaveMode.Full)
            'Load lại Config
            ConfigurationManager.RefreshSection("connectionStrings")
            'Load lại datacontext
            dc = New TanNamChinhDataContext
        Catch ex As Exception
            Throw ex
        End Try
        Return connectString
    End Function

    Public Shared Function GetGiaTriThanhPhan(ByVal connectionString As String, ByVal pName As String) As String
        'Dim regex As Regex
        'Dim pattern As String = ""
        Dim KQ As String = ""
        Dim strTP As String = ""

        Dim data() As String = connectionString.Split(";")
        For i As Integer = 0 To data.GetUpperBound(0)
            If data(i).IndexOf(pName) > -1 Then
                strTP = data(i)
                Exit For
            End If
        Next
        KQ = strTP.Replace(pName + "=", "")
        'Dim data2() As String = strTP.Split("=")
        'If data2.GetUpperBound(0) > 0 Then
        '    KQ = data2(1)
        'End If
        Return KQ
    End Function

    Private Shared Function EnCrypt(ByVal strEnCrypt As String, ByVal key As String) As String
        Try
            Dim keyArr As Byte()
            Dim EnCryptArr As Byte() = UTF8Encoding.UTF8.GetBytes(strEnCrypt)
            Dim MD5Hash As New MD5CryptoServiceProvider()
            keyArr = MD5Hash.ComputeHash(UTF8Encoding.UTF8.GetBytes(key))
            Dim tripDes As New TripleDESCryptoServiceProvider()
            tripDes.Key = keyArr
            tripDes.Mode = CipherMode.ECB
            tripDes.Padding = PaddingMode.PKCS7
            Dim transform As ICryptoTransform = tripDes.CreateEncryptor()
            Dim arrResult As Byte() = transform.TransformFinalBlock(EnCryptArr, 0, EnCryptArr.Length)
            Return Convert.ToBase64String(arrResult, 0, arrResult.Length)
        Catch ex As Exception
        End Try
        Return ""
    End Function

    Private Shared Function DeCrypt(ByVal strDecypt As String, ByVal key As String) As String
        Try
            Dim keyArr As Byte()
            Dim DeCryptArr As Byte() = Convert.FromBase64String(strDecypt)
            Dim MD5Hash As New MD5CryptoServiceProvider()
            keyArr = MD5Hash.ComputeHash(UTF8Encoding.UTF8.GetBytes(key))
            Dim tripDes As New TripleDESCryptoServiceProvider()
            tripDes.Key = keyArr
            tripDes.Mode = CipherMode.ECB
            tripDes.Padding = PaddingMode.PKCS7
            Dim transform As ICryptoTransform = tripDes.CreateDecryptor()
            Dim arrResult As Byte() = transform.TransformFinalBlock(DeCryptArr, 0, DeCryptArr.Length)
            Return UTF8Encoding.UTF8.GetString(arrResult)
        Catch ex As Exception
        End Try
        Return ""
    End Function
End Class
